import cPickle

from common import *
from common.terrain import Terrain
import units
import buildings
import doodads

class Map(object):
	"""
	This class encapsulates all the elements of a map.
	"""
	
	def __init__(self):
		self.description = ''
		
		self.terrain = Terrain(self)
		self.units = []
		self.buildings = []
		self.doodads = []
		
		# Win conditions
		self.ctf_win = False
		self.destroy_all_win = True
		self.horn_win = False
	
	def remove(self, gameObject):
		if issubclass(gameObject.__class__, units.AbstractUnit):
			try:
				self.terrain.desoccupy(gameObject)
				self.units.remove(gameObject)
			except: pass
			
		if issubclass(gameObject.__class__, buildings.AbstractBuilding):
			try:
				self.terrain.desoccupy(gameObject)
				self.buildings.remove(gameObject)
			except: pass
			
		if issubclass(gameObject.__class__, doodads.AbstractDoodad):
			try:
				self.terrain.desoccupy(gameObject)
				self.doodads.remove(gameObject)
			except: pass
	
	def save(self, filename):
		try:
			file = open(filename, 'w')
			
			cPickle.dump(self.description, file)
			cPickle.dump(self.terrain.vertices, file)
			cPickle.dump(self.ctf_win, file)
			cPickle.dump(self.destroy_all_win, file)
			cPickle.dump(self.horn_win, file)
			for unit in self.units:
				cPickle.dump('Unit', file)
				cPickle.dump(unit.__class__, file)
				cPickle.dump(unit.top_left_block.id, file)
				cPickle.dump(unit.team, file)
			for building in self.buildings:
				cPickle.dump('Building', file)
				cPickle.dump(building.__class__, file)
				cPickle.dump(building.top_left_block.id, file)
				cPickle.dump(building.team, file)
			for doodad in self.doodads:
				cPickle.dump('Doodad', file)
				cPickle.dump(doodad.__class__, file)
				cPickle.dump(doodad.top_left_block.id, file)
			cPickle.dump(None, file)
			
			file.close()
		except:
			# TODO: Print the exception?
			return False
		
		return True
	
	
	def load(self, filename):
		try:
			file = open(filename, 'r')
			
			# Parse pickle file
			description = cPickle.load(file)
			vertices = cPickle.load(file)
			ctf_win = cPickle.load(file)
			destroy_all_win = cPickle.load(file)
			horn_win = cPickle.load(file)
			parsedUnits = []
			parsedBuildings = []
			parsedDoodads = []
			
			next = cPickle.load(file)
			while not(next is None):
				if next == 'Unit':
					unit = cPickle.load(file)
					block_id = cPickle.load(file)
					team = cPickle.load(file)
					parsedUnits.append((unit, block_id, team))
				elif next == 'Building':
					building = cPickle.load(file)
					block_id = cPickle.load(file)
					team = cPickle.load(file)
					parsedBuildings.append((building, block_id, team))
				if next == 'Doodad':
					doodad = cPickle.load(file)
					block_id = cPickle.load(file)
					parsedDoodads.append((doodad, block_id))
				next = cPickle.load(file)
				
			file.close()
			
			newTerrain = Terrain(self)				 
			newTerrain.load_vertices(vertices)
			
			# Create units/buildings/doodads objects
			units = []
			buildings = []
			doodads = []
			
			for args in parsedUnits:
				unit = args[0](newTerrain.blocks[args[1][X]][args[1][Y]], args[2])
				units.append(unit)
				newTerrain.occupy(unit)
			
			for args in parsedBuildings:
				building = args[0](newTerrain.blocks[args[1][X]][args[1][Y]], args[2])
				buildings.append(building)
				newTerrain.occupy(building)
				
			for args in parsedDoodads:
				doodad = args[0](newTerrain.blocks[args[1][X]][args[1][Y]])
				doodads.append(doodad)
				newTerrain.occupy(doodad)
			
			# Just change the attributes when we are done.
			self.description = description
			self.terrain = newTerrain
			self.ctf_win = ctf_win
			self.destroy_all_win = destroy_all_win
			self.horn_win = horn_win
			self.units = units
			self.buildings = buildings
			self.doodads = doodads
		except Exception, e:
			# TODO: Print the exception?
			return False
		
		return True